<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>
<body>
    为什么要学习预解析?
    两步:1.先预编译 2,逐行执行
    <script>
        // 1.为什么变量会有提升功能,同时输入一个undefined?
        // console.log(a);//undefined
        // var a;

        // 2.为什么声明式的函数可以在任何的地方被调用呢?
        // fn()
        // function fn(){
        //     alert(1)
        // }
        // fn()
    </script>

    学习预解析:
    分成2个步骤:
    1.预编译:代码进入到浏览器进行逐行执行的之前要干的事情,(不可见)
    1-1,预编译分析:
    var a=1;
    a会先找到var 和 function 关键字,找到var之后,提前赋值undefined

    fn()=function fn(){}
    找到function,提前将整个函数赋值给函数的名字.

    2.逐行执行:代码进入到浏览器,可以根据浏览器返回的信息,去查看对应的结果,同时遇到错误代码,立刻停止执行

    案例1:
    <script>
        // 预解析:
        // 先找var,提前赋值undefined.
        // 找function fn,fn=function fn(){console.log("hanshu");}
        //console.log(a);//undefined
        // fn();//console.log("函数");
        // var a=10;
        // function fn(){
        //     console.log("函数");
        // }
        // fn();//console.log("函数");

    </script>

    案例2:
    规则:如果预编译函数名和变量名出现重复的情况下,函数名优先(干掉变量名)
    函数名称如果没有被调用,这函数没用
    <script>
        // 1.预编译:
        // 先找var  a  undefined;
        // 找function, a()=function a(){console.log("函数");}

        // 2.逐行执行
        // 看到函数名 发现函数户名也是a,函数名干掉变量名,干掉undefined
        // a就是函数

        // console.log(a);//函数体
        // a();
        // var a=10;//把a变层10
        // function a(){
        //     console.log("函数");
        // }
        // a();//10()
        // console.log(a);
    </script>

    案例3:
    变量的访问
    <script>
        // var a=10;
        // function fn(){
        //     var b=10;//函数里面的声明的变量外面无法获取到的
        //     console.log(a);//函数内部可以访问到函数外部的变量的
        // }
        // fn();
        // console.log(b);//Uncaught ReferenceError: b is not defined
        //说明:fn的函数执行完,就不见了,所以从函数外部拿不到的.
    </script>

    案例4:
    <script>
        // var a=10;
        // function fn(a){
        //     //函数的参数相当于这个函数内部的变量,预编译
        //     //相当于在这里var a=10; 有一个var a
        //     a=20;
        //     console.log(a);//20
        // }
        // console.log(a);//10;
        // fn(a);//fn(10);将外部的变量a=10,当做实参传到了函数的内部
    </script>

    <script>
        // 第四题：
        var x = 999999;
        var y = 9999;
        var z = 99;
        function add(n) {
        n = n + 1;
        return n;
        }
        y = add(x);
        console.log(y);
        function add(n) {
        n = n + 3;
        }
        z = add(x);
        console.log(z);
    </script>


<script>
    alert(a);//function a() {alert(5);}
    a();//5
    var a = 3;

    function a() {
        alert(10);
    }
    alert(a);//3
    function a() {
        alert(5);
    }
    a = 6;
    alert(a);//6
    var a = function() {
        alert(8);
    }
    a();//8
</script>
</body>
</html>